/* **********************************************************************************
 *
 * Copyright (c) TMF.AscendedThemeKit.Unthemed.NET Project. All rights reserved.
 *
 * This source code is subject to terms and conditions of the Shared Source License
 * for TMF.AscendedThemeKit.Unthemed. A copy of the license can be found in the License.html file
 * at the root of this distribution. If you can not locate the Shared Source License
 * for TMF.AscendedThemeKit.Unthemed, please send an email to ascendlic@<TBD>.
 * By using this source code in any fashion, you are agreeing to be bound by
 * the terms of the Shared Source License for TMF.AscendedThemeKit.Unthemed.NET.
 *
 * You must not remove this notice, or any other, from this software.
 *
 * **********************************************************************************/

using TMF.AscendedThemeKit.Unthemed.Resources;
using System;
using System.Collections;
using System.Collections.Generic;
using System.ComponentModel;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Globalization;
using System.Runtime.InteropServices;
using System.Text;
using System.Windows.Forms;
using System.Diagnostics;
using System.ComponentModel.Design;

namespace TMF.AscendedThemeKit.Unthemed.Windows.Forms
{
    /// <summary>
    /// Represents a Windows navigation button control group with associated panels.
    /// </summary>
    [ToolboxBitmap(typeof(NavigationPane), "NavigationPane.ico")]
    [ResourceDescriptionAttribute("NavigationPaneDescription")]
    [DefaultEvent("SelectedNavigationButtonChanged")]
    [DefaultProperty("NavigationPages")]
#if GENERAL_RELEASE
    [Designer(typeof(Ascend.Windows.Forms.Design.NavigationPaneDesigner), typeof(IDesigner))]
#else
    [Designer("TMF.AscendedThemeKit.Unthemed.Windows.Forms.Design.NavigationPaneDesigner, TMF.AscendedThemeKit.Unthemed.Design.v1.5, Culture=neutral, PublicKeyToken=5123e2ac4258b06a", typeof(IDesigner))]
#endif
    [DesignerCategory("Form")]
    public class NavigationPane : System.Windows.Forms.ScrollableControl
    {
        private NavigationPaneRender _render;
        private NavigationPageCollection _navigationPageCollection;
        private int _activeNavigationPanePageIndex;
        private ToolTip _toolTip;
        private System.Windows.Forms.ContextMenuStrip _contextMenuStrip;
        private System.Windows.Forms.ToolStripMenuItem _showMoreButtonsToolStripMenuItem;
        private System.Windows.Forms.ToolStripMenuItem _showFewerButtonsToolStripMenuItem;
        private System.Windows.Forms.ToolStripMenuItem _navigationPaneOptionsToolStripMenuItem;
        private System.Windows.Forms.ToolStripMenuItem _addOrRemoveButtonsToolStripMenuItem;
        private System.Windows.Forms.ToolStripSeparator _mainDivider;
        private bool _mouseDown;
        private int _visibleButtonCount;
        private int _maxVisibleButtonCount;
        private ImageList _imageList;
        private ImageList _imageListFooter;
        private bool _displayOptionsMenuItem;
        private bool _disposed;
        private bool _displayAddOrRemoveMenuItem = true;
        private bool _resetDisplayOrder;
        private string _currentDisplayOrderName;
        private NavigationPaneFooterProperty _footerProperty;
        private NavigationPaneCaptionProperty _captionProperty;
        private NavigationPaneButtonProperty _buttonProperty;
        private NavigationPaneSplitBarProperty _splitBarProperty;
        private bool _blockMouseMove;
        private bool _initialPaint = true;
        private string _initialFontName;
		private int _minimizedWidth;
		private bool _isMinimized;
		private bool _allowMinimize = true;

        /// <summary>
        /// Occurs when the AntiAlias property changes.
        /// </summary>
        [ResourceDescriptionAttribute("AntiAliasChangedDescription"), ResourceCategoryAttribute("PropertyChangedCategory"), ResourceDisplayName("DisplayNameAntiAliasChanged")]
        public event EventHandler AntiAliasChanged;

        /// <summary>
        /// Occurs when the Border property changes.
        /// </summary>
        [ResourceDescriptionAttribute("BorderChangedDescription"), ResourceCategoryAttribute("PropertyChangedCategory"), ResourceDisplayName("DisplayNameBorderChanged")]
        public event EventHandler BorderChanged;

        /// <summary>
        /// Occurs when the BorderColor property changes.
        /// </summary>
        [ResourceDescriptionAttribute("BorderColorChangedDescription"), ResourceCategoryAttribute("PropertyChangedCategory"), ResourceDisplayName("DisplayNameBorderColorChanged")]
        public event EventHandler BorderColorChanged;

        /// <summary>
        /// Occurs when a NavigationPanePage is deselected.
        /// </summary>
        [ResourceDescriptionAttribute("DeselectedDescription"), ResourceCategoryAttribute("ActionCategory"), ResourceDisplayName("DisplayNameDeselected")]
        public event EventHandler<NavigationPaneEventArgs> Deselected;

        /// <summary>
        /// Occurs before a NavigationPanePage is deselected, enabling a handler to cancel the NavigationPanePage change. 
        /// </summary>
        [ResourceDescriptionAttribute("DeselectingDescription"), ResourceCategoryAttribute("ActionCategory"), ResourceDisplayName("DisplayNameDeselecting")]
        public event EventHandler<NavigationPaneCancelEventArgs> Deselecting;

		/// <summary>
		/// Occurs after the NavigationPane is maximized.
		/// </summary>
		[ResourceDescriptionAttribute("MaximizedDescription"), ResourceCategoryAttribute("ActionCategory"), ResourceDisplayName("Maximized")]
		public event EventHandler Maximized;

		/// <summary>
		/// Occurs after the NavigationPane is minimized.
		/// </summary>
		[ResourceDescriptionAttribute("MinimizedDescription"), ResourceCategoryAttribute("ActionCategory"), ResourceDisplayName("Minimized")]
		public event EventHandler Minimized;

        /// <summary>
        /// Raised when the active navigation button index changes.
        /// </summary>
        [ResourceDescriptionAttribute("SelectedIndexChangedDescription"), ResourceCategoryAttribute("BehaviorCategory"), ResourceDisplayName("DisplayNameSelectedIndexChanged")]
        public event EventHandler SelectedIndexChanged;

        /// <summary>
        /// Occurs before a NavigationPanePage is selected, enabling a handler to cancel the NavigationPanePage change. 
        /// </summary>
        [ResourceDescriptionAttribute("SelectingDescription"), ResourceCategoryAttribute("ActionCategory"), ResourceDisplayName("DisplayNameSelecting")]
        public event EventHandler<NavigationPaneCancelEventArgs> Selecting;

        /// <summary>
        /// Occurs when a NavigationPanePage is selected.
        /// </summary>
        [ResourceDescriptionAttribute("SelectedDescription"), ResourceCategoryAttribute("ActionCategory"), ResourceDisplayName("DisplayNameSelected")]
        public event EventHandler<NavigationPaneEventArgs> Selected;

        /// <summary>
        /// Gets or sets if the add or remove menum item is visible on the control.
        /// </summary>
        [ResourceCategoryAttribute("BehaviorCategory"), ResourceDescriptionAttribute("AllowAddOrRemoveDescription"), ResourceDisplayName("DisplayNameAllowAddOrRemove"), DefaultValueAttribute(true)]
        public bool AllowAddOrRemove
        {
            get
            {
                return this._displayAddOrRemoveMenuItem;

            }

            set
            {
                if (this._displayAddOrRemoveMenuItem == value)
                {
                    return;

                }

                this._displayAddOrRemoveMenuItem = value;
                this._addOrRemoveButtonsToolStripMenuItem.Visible = this._displayAddOrRemoveMenuItem;

            }

        }

        /// <summary>
        /// Gets or sets if the options menum item is visible on the control.
        /// </summary>
        [ResourceCategoryAttribute("BehaviorCategory"), ResourceDescriptionAttribute("AllowOptionsDescription"), ResourceDisplayName("DisplayNameAllowOptions"), DefaultValueAttribute(true)]
        public bool AllowOptions
        {
            get
            {
                return this._displayOptionsMenuItem;

            }

            set
            {
                if (this._displayOptionsMenuItem == value)
                {
                    return;

                }

                this._displayOptionsMenuItem = value;
                this._navigationPaneOptionsToolStripMenuItem.Visible = this._displayOptionsMenuItem;

            }

        }

        /// <summary>
        /// Specifies the rendering hint for the control.
        /// </summary>
        /// <value>
        /// 	<para>
        /// System.Boolean . Specifies if the rendering should use antialiasing.
        /// </para>
        /// 	<para>
        /// This property is read/write. 
        /// </para>
        /// </value>
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("AntiAliasDescription"), ResourceDisplayName("DisplayNameAntiAlias"), DefaultValueAttribute(false)]
        public bool AntiAlias
        {
            get
            {
                return this._render.AntiAlias;

            }

            set
            {
                if (value == this._render.AntiAlias)
                {
                    return;

                }

                this._render.AntiAlias = value;

                base.Invalidate();

                this.OnAntiAliasChanged(new EventArgs());

            }

        }

        /// <summary>
        /// Gets or sets the border for the control.
        /// </summary>
        /// <value>
        /// 	<para>
        /// Border. An object of type Border representing the control's border width characteristics.
        /// </para>
        /// 	<para>
        /// This property is read/write.
        /// </para>
        /// </value>
        /// <remarks>
        /// For containers such as GradientPanel and GradientCaption, the Border property gets or sets their respective border widths inside the DisplayRectangle.
        /// </remarks>
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("BorderDescription"), ResourceDisplayName("DisplayNameBorder"), DefaultValueAttribute(typeof(Border), "1, 1, 1, 1")]
        public Border Border
        {
            get
            {
                return this._render.Border;

            }

            set
            {
                if (value == this._render.Border)
                {
                    return;

                }

                this._render.Border = value;

                base.Invalidate();

                this.OnBorderChanged(new EventArgs());

            }

        }

        /// <summary>
        /// Gets or sets the border color(s) for the control.
        /// </summary>
        /// <value>
        /// 	<para>
        /// BorderColor. An object of type Border representing the control's border color characteristics.
        /// </para>
        /// 	<para>
        /// This property is read/write.
        /// </para>
        /// </value>
        /// <remarks>
        /// For containers such as GradientPanel and GradientCaption, the BorderColor property gets or sets their respective border colors inside the DisplayRectangle.
        /// </remarks>
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("BorderColorDescription"), ResourceDisplayName("DisplayNameBorderColor"), DefaultValueAttribute(typeof(BorderColor), "Left=Color [ActiveCaption],Top=Color [ActiveCaption],Right=Color [ActiveCaption],Bottom=Color [ActiveCaption]")]
        public BorderColor BorderColor
        {
            get
            {
                return this._render.BorderColor;

            }

            set
            {
                if (value == this._render.BorderColor)
                {
                    return;

                }

                this._render.BorderColor = value;

                base.Invalidate();

                this.OnBorderColorChanged(EventArgs.Empty);

            }

        }

        /// <summary>
        /// Gets or sets the button properties.
        /// </summary>
        [DesignOnlyAttribute(true), EditorBrowsableAttribute(EditorBrowsableState.Never), ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("ButtonDescription"), ResourceDisplayName("DisplayNameButton")]
        public NavigationPaneButtonProperty Button
        {
            get
            {
                return this._buttonProperty;

            }

            set
            {
                this._buttonProperty = value;

            }

        }

        /// <summary>
        /// Determines if the Button property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>true or false</returns>
        public bool ShouldSerializeButton()
        {
            return ((this._render.ButtonHeight != 32) || (this._render.ButtonGradientHighColor != SystemColors.ButtonHighlight) || (this._render.ButtonGradientLowColor != SystemColors.GradientActiveCaption) || (this._render.ButtonBorderColor != SystemColors.MenuHighlight) || (this._render.ButtonForeColor != SystemColors.ControlText) || (this._render.ButtonHighlightGradientHighColor != Color.White) || (this._render.ButtonHighlightGradientLowColor != Color.FromArgb(255, 165, 78)) || (this._render.ButtonActiveGradientHighColor != Color.FromArgb(255, 225, 155)) || (this._render.ButtonActiveGradientLowColor != Color.FromArgb(255, 165, 78)) || (this._render.ButtonTextAlign != ContentAlignment.MiddleLeft) || (this._render.ButtonImageAlign != ContentAlignment.MiddleLeft));

        }

        /// <summary>
        /// Resets the button to default values.
        /// </summary>
        public void ResetButton()
        {
            this.ButtonHeight = 32;
            this.ButtonGradientHighColor = SystemColors.ButtonHighlight;
            this.ButtonGradientLowColor = SystemColors.GradientActiveCaption;
            this.ButtonBorderColor = SystemColors.MenuHighlight;
            this.ButtonForeColor = SystemColors.ControlText;
            this.ButtonHighlightGradientHighColor = Color.White;
            this.ButtonHighlightGradientLowColor = Color.FromArgb(255, 165, 78);
            this.ButtonActiveGradientHighColor = Color.FromArgb(255, 225, 155);
            this.ButtonActiveGradientLowColor = Color.FromArgb(255, 165, 78);
            this.ButtonTextAlign = ContentAlignment.MiddleLeft;
            this.ButtonImageAlign = ContentAlignment.MiddleLeft;

            base.Invalidate();

        }

        /// <summary>
        /// Gets or set button active gradient high color.
        /// </summary>
        [Browsable(false)]
        public Color ButtonActiveGradientHighColor
        {
            get
            {
                return this._render.ButtonActiveGradientHighColor;

            }

            set
            {
                if (this._render.ButtonActiveGradientHighColor == value)
                {
                    return;

                }

                Color oldColor = this._render.ButtonActiveGradientHighColor;

                this._render.ButtonActiveGradientHighColor = value;

                this.SetDefaultButtonActiveGradientHighColor(oldColor, value);

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or set button active gradient low color.
        /// </summary>
        [Browsable(false)]
        public Color ButtonActiveGradientLowColor
        {
            get
            {
                return this._render.ButtonActiveGradientLowColor;

            }

            set
            {
                if (this._render.ButtonActiveGradientLowColor == value)
                {
                    return;

                }

                Color oldColor = this._render.ButtonActiveGradientLowColor;

                this._render.ButtonActiveGradientLowColor = value;

                this.SetDefaultButtonActiveGradientLowColor(oldColor, value);

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the button border color on the control.
        /// </summary>
        [Browsable(false)]
        public Color ButtonBorderColor
        {
            get
            {
                return this._render.ButtonBorderColor;

            }

            set
            {
                if (this._render.ButtonBorderColor == value)
                {
                    return;

                }

                this._render.ButtonBorderColor = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the forecolor associated with the buttons.
        /// </summary>
        [Browsable(false)]
        public Color ButtonForeColor
        {
            get
            {
                return this._render.ButtonForeColor;

            }

            set
            {
                if (this._render.ButtonForeColor == value)
                {
                    return;

                }

                Color oldColor = this._render.ButtonForeColor;

                this._render.ButtonForeColor = value;

                this.SetDefaultButtonForeColor(oldColor, value);

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the font associated with the buttons.
        /// </summary>
        [Browsable(false)]
        public Font ButtonFont
        {
            get
            {
                return this._render.ButtonFont;

            }

            set
            {
                if (value == null)
                {
                    return;

                }

                if (this._render.ButtonFont == value)
                {
                    return;

                }

                this._render.ButtonFont = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Determines if the ButtonFont property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>always true</returns>
        public bool ShouldSerializeButtonFont()
        {
            return true;

        }

        /// <summary>
        /// Gets or sets the button gradient high color on the control.
        /// </summary>
        [Browsable(false)]
        public Color ButtonGradientHighColor
        {
            get
            {
                return this._render.ButtonGradientHighColor;

            }

            set
            {
                if (this._render.ButtonGradientHighColor == value)
                {
                    return;

                }

                Color oldColor = this._render.ButtonGradientHighColor;

                this._render.ButtonGradientHighColor = value;

                this.SetDefaultButtonGradientHighColor(oldColor, value);

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the button gradient low color.
        /// </summary>
        [Browsable(false)]
        public Color ButtonGradientLowColor
        {
            get
            {
                return this._render.ButtonGradientLowColor;

            }

            set
            {
                if (this._render.ButtonGradientLowColor == value)
                {
                    return;

                }

                Color oldColor = this._render.ButtonGradientLowColor;

                this._render.ButtonGradientLowColor = value;

                this.SetDefaultButtonGradientLowColor(oldColor, value);

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the navigation button height on the control.
        /// </summary>
        [Browsable(false)]
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("ButtonHeightDescription"), ResourceDisplayName("DisplayNameButtonHeight"), DefaultValueAttribute(32)]
        public int ButtonHeight
        {
            get
            {
                return this._render.ButtonHeight;

            }

            set
            {
                if (this._render.ButtonHeight == value)
                {
                    return;

                }

                this._render.ButtonHeight = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the gradient high (lighter) color for the button when it is moused over.
        /// </summary>
        [Browsable(false)]
        public Color ButtonHighlightGradientHighColor
        {
            get
            {
                return this._render.ButtonHighlightGradientHighColor;

            }

            set
            {
                if (this._render.ButtonHighlightGradientHighColor == value)
                {
                    return;

                }

                Color oldColor = this._render.ButtonHighlightGradientHighColor;

                this._render.ButtonHighlightGradientHighColor = value;

                this.SetDefaultButtonHighlightGradientHighColor(oldColor, value);

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the gradient low (darker) color for the button when it is moused over.
        /// </summary>
        [Browsable(false)]
        public Color ButtonHighlightGradientLowColor
        {
            get
            {
                return this._render.ButtonHighlightGradientLowColor;

            }

            set
            {
                if (this._render.ButtonHighlightGradientLowColor == value)
                {
                    return;

                }

                Color oldColor = this._render.ButtonHighlightGradientLowColor;

                this._render.ButtonHighlightGradientLowColor = value;

                this.SetDefaultButtonHighlightGradientLowColor(oldColor, value);

                base.Invalidate();

            }

        }

        /// <summary>
        /// The ContentAlignment associated with the button's image.
        /// </summary>
        /// <value>
        /// <para>
        /// System.Drawing.ContentAlignment . The ContentAlignment associated with the button's image.
        /// </para>
        /// <para>
        /// This property is read/write. 
        /// </para>
        /// </value>
        [Browsable(false)]
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("ImageAlignmentDescription"), ResourceDisplayName("DisplayNameImageAlign"), DefaultValueAttribute(ContentAlignment.MiddleLeft)]
        public ContentAlignment ButtonImageAlign
        {
            get
            {
                return this._render.ButtonImageAlign;

            }

            set
            {
                if (this._render.ButtonImageAlign == value)
                {
                    return;

                }

                ContentAlignment oldAlignment = this._render.ButtonImageAlign;

                this._render.ButtonImageAlign = value;

                this.SetDefaultButtonImageAlign(oldAlignment, value);

                base.Invalidate();

            }

        }

        /// <summary>
        /// The ContentAlignment associated with the button's text.
        /// </summary>
        /// <value>
        /// <para>
        /// System.Drawing.ContentAlignment . The ContentAlignment associated with the button's text.
        /// </para>
        /// <para>
        /// This property is read/write. 
        /// </para>
        /// </value>
        [Browsable(false)]
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("TextAlignmentDescription"), ResourceDisplayName("DisplayNameTextAlign"), DefaultValueAttribute(ContentAlignment.MiddleLeft)]
        public ContentAlignment ButtonTextAlign
        {
            get
            {
                return this._render.ButtonTextAlign;

            }

            set
            {
                if (this._render.ButtonTextAlign == value)
                {
                    return;

                }

                ContentAlignment oldAlignment = this._render.ButtonTextAlign;

                this._render.ButtonTextAlign = value;

                this.SetDefaultButtonTextAlign(oldAlignment, value);

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the border color associated with the caption.
        /// </summary>
        [Browsable(false)]
        public Color CaptionBorderColor
        {
            get
            {
                return this._render.CaptionBorderColor;

            }

            set
            {
                if (this._render.CaptionBorderColor == value)
                {
                    return;

                }

                this._render.CaptionBorderColor = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the font associated with the caption.
        /// </summary>
        [Browsable(false)]
        public Font CaptionFont
        {
            get
            {
                return this._render.CaptionFont;

            }

            set
            {
                if (value == null)
                {
                    return;

                }

                if (this._render.CaptionFont == value)
                {
                    return;

                }

                this._render.CaptionFont = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Determines if the CaptionFont property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>always true</returns>
        public bool ShouldSerializeCaptionFont()
        {
            return true;

        }

        /// <summary>
        /// Gets or sets the forecolor associated with the caption.
        /// </summary>
        [Browsable(false)]
        public Color CaptionForeColor
        {
            get
            {
                return this._render.CaptionForeColor;

            }

            set
            {
                if (this._render.CaptionForeColor == value)
                {
                    return;

                }

                this._render.CaptionForeColor = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the caption height on the control.
        /// </summary>
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("CaptionHeightDescription"), ResourceDisplayName("DisplayNameCaptionHeight"), DefaultValueAttribute(26)]
        [Browsable(false)]
        public int CaptionHeight
        {
            get
            {
                return this._render.CaptionHeight;

            }

            set
            {
                if (this._render.CaptionHeight == value)
                {
                    return;

                }

                this._render.CaptionHeight = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// The ContentAlignment associated with this controls image.
        /// </summary>
        /// <value>
        /// <para>
        /// System.Drawing.ContentAlignment . The ContentAlignment associated with this controls image.
        /// </para>
        /// <para>
        /// This property is read/write. 
        /// </para>
        /// </value>
        [Browsable(false)]
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("ImageAlignmentDescription"), ResourceDisplayName("DisplayNameImageAlign"), DefaultValueAttribute(ContentAlignment.MiddleRight)]
        public ContentAlignment CaptionImageAlign
        {
            get
            {
                return this._render.CaptionImageAlign;

            }

            set
            {
                if (this._render.CaptionImageAlign == value)
                {
                    return;

                }

                this._render.CaptionImageAlign = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// The ContentAlignment associated with the caption's text.
        /// </summary>
        /// <value>
        /// <para>
        /// System.Drawing.ContentAlignment . The ContentAlignment associated with the caption's text.
        /// </para>
        /// <para>
        /// This property is read/write. 
        /// </para>
        /// </value>
        [Browsable(false)]
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("TextAlignmentDescription"), ResourceDisplayName("DisplayNameTextAlign"), DefaultValueAttribute(ContentAlignment.MiddleLeft)]
        public ContentAlignment CaptionTextAlign
        {
            get
            {
                return this._render.CaptionTextAlign;

            }

            set
            {
                if (this._render.CaptionTextAlign == value)
                {
                    return;

                }

                this._render.CaptionTextAlign = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the caption gradient high color on the control.
        /// </summary>
        [Browsable(false)]
        public Color CaptionGradientHighColor
        {
            get
            {
                return this._render.CaptionGradientHighColor;

            }

            set
            {
                if (this._render.CaptionGradientHighColor == value)
                {
                    return;

                }

                this._render.CaptionGradientHighColor = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the caption gradient low color.
        /// </summary>
        [Browsable(false)]
        public Color CaptionGradientLowColor
        {
            get
            {
                return this._render.CaptionGradientLowColor;

            }

            set
            {
                if (this._render.CaptionGradientLowColor == value)
                {
                    return;

                }

                this._render.CaptionGradientLowColor = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Specifies the direction of a linear gradient for the caption.
        /// </summary>
        /// <value>
        /// 	<para>
        /// System.Drawing.Drawing2D.LinearGradientMode . Specifies the direction of a linear gradient.
        /// </para>
        /// 	<para>
        /// This property is read/write. 
        /// </para>
        /// </value>
        [Browsable(false)]
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("CaptionGradientModeDescription"), ResourceDisplayName("DisplayNameCaptionGradientMode"), DefaultValueAttribute(LinearGradientMode.Vertical)]
        public LinearGradientMode CaptionGradientMode
        {
            get
            {
                return this._render.CaptionGradientMode;

            }

            set
            {
                if (value == this._render.CaptionGradientMode)
                {
                    return;

                }

                this._render.CaptionGradientMode = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets the default initial size of the control.
        /// </summary>
        protected override Size DefaultSize
        {
            get
            {
                return new Size(150, 300);

            }

        }

        /// <summary>
        /// Gets or sets the footer properties.
        /// </summary>
        [DesignOnlyAttribute(true), EditorBrowsableAttribute(EditorBrowsableState.Never), ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("FooterDescription"), ResourceDisplayName("DisplayNameFooter")]
        public NavigationPaneFooterProperty Footer
        {
            get
            {
                return this._footerProperty;

            }

            set
            {
                this._footerProperty = value;

            }

        }

        /// <summary>
        /// Determines if the Footer property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>true or false</returns>
        public bool ShouldSerializeFooter()
        {
            return ((this._render.FooterHeight != 30) || (this._render.FooterGradientHighColor != SystemColors.ButtonHighlight) || (this._render.FooterGradientLowColor != SystemColors.GradientActiveCaption) || (this._render.FooterHighlightGradientHighColor != Color.White) || (this._render.FooterHighlightGradientLowColor != Color.FromArgb(255, 255, 165, 78)));

        }

        /// <summary>
        /// Resets the footer to default values.
        /// </summary>
        public void ResetFooter()
        {
            this._render.FooterHeight = 30;
            this._render.FooterGradientHighColor = SystemColors.ButtonHighlight;
            this._render.FooterGradientLowColor = SystemColors.GradientActiveCaption;
            this._render.FooterHighlightGradientHighColor = Color.White;
            this._render.FooterHighlightGradientLowColor = Color.FromArgb(255, 255, 165, 78);

            base.Invalidate();

        }

        /// <summary>
        /// Gets or sets the footer gradient high color.
        /// </summary>
        [Browsable(false)]
        public Color FooterGradientHighColor
        {
            get
            {
                return this._render.FooterGradientHighColor;

            }

            set
            {
                if (this._render.FooterGradientHighColor == value)
                {
                    return;

                }

                this._render.FooterGradientHighColor = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the footer gradient low color.
        /// </summary>
        [Browsable(false)]
        public Color FooterGradientLowColor
        {
            get
            {
                return this._render.FooterGradientLowColor;

            }

            set
            {
                if (this._render.FooterGradientLowColor == value)
                {
                    return;

                }

                this._render.FooterGradientLowColor = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the gradient high (lighter) color for the footer when it is moused over.
        /// </summary>
        /// <value>
        /// <para>
        /// System.Drawing.Color . A Color that represents the gradient high color of the footer when it is moused over.
        /// </para>
        /// <para>
        /// This property is read/write. 
        /// </para>
        /// </value>
        [Browsable(false)]
        public Color FooterHighlightGradientHighColor
        {
            get
            {
                return this._render.FooterHighlightGradientHighColor;

            }

            set
            {
                if (value == this._render.FooterHighlightGradientHighColor)
                {
                    return;

                }

                this._render.FooterHighlightGradientHighColor = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the gradient low (darker) color for the footer when it is moused over.
        /// </summary>
        /// <value>
        /// <para>
        /// System.Drawing.Color . A Color that represents the gradient low color of the footer when it is moused over.
        /// </para>
        /// <para>
        /// This property is read/write. 
        /// </para>
        /// </value>
        [Browsable(false)]
        public Color FooterHighlightGradientLowColor
        {
            get
            {
                return this._render.FooterHighlightGradientLowColor;

            }

            set
            {
                if (value == this._render.FooterHighlightGradientLowColor)
                {
                    return;

                }

                this._render.FooterHighlightGradientLowColor = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the footer height on the control.
        /// </summary>
        [Browsable(false)]
        public int FooterHeight
        {
            get
            {
                return this._render.FooterHeight;

            }

            set
            {
                if (this._render.FooterHeight == value)
                {
                    return;

                }

                this._render.FooterHeight = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets the NavigationPanePage rectangle.
        /// </summary>
        /// <remarks>
        /// The property is read only.
        /// </remarks>
        [Browsable(false), DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
        public Rectangle NavigationPageRectangle
        {
            get
            {
                int bottomHeight = (this.FooterHeight + (this._render.DisplayButtonCount * this.ButtonHeight) + this.SplitBarHeight + this.Border.Bottom);

                return new Rectangle(this.Border.Left, (this.Border.Top + this.CaptionHeight), (this.Width - (this.Border.Left + this.Border.Right)), (this.Height - this.Border.Top - this.CaptionHeight - bottomHeight));

            }

        }

        /// <summary>
        /// A collection of pages used in the navigation pane.
        /// </summary>
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("NavigationPageCollectionDescription"), ResourceDisplayName("DisplayNameNavigationPages"), DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
        public NavigationPageCollection NavigationPages
        {
            get
            {
                return this._navigationPageCollection;

            }

        }

        /// <summary>
        /// Represents the currently active navigation page.
        /// </summary>
        /// <value>
        /// </value>
        [Browsable(false), DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
        public NavigationPanePage SelectedNavigationPage
        {
            get
            {
                int index = this._navigationPageCollection.IndexOf(this._render.DisplayOrder[this._activeNavigationPanePageIndex].ToString());

                return this._navigationPageCollection[index];

            }

            set
            {
                if (value != null)
                {
                    if (this._navigationPageCollection.Contains(value))
                    {
                        if (this._render.DisplayOrder.Contains(value.Name))
                        {
                            this.SelectedIndex = this._render.DisplayOrder.IndexOf(value.Name);

                        }

                    }

                }

            }

        }

        /// <summary>
        /// Represents the index of the currently active navigation button.
        /// </summary>
        [SettingsBindableAttribute(true)]
        [Browsable(false), DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
        public int SelectedIndex
        {
            get
            {
                return this._activeNavigationPanePageIndex;

            }

            set
            {
                if (value == this._activeNavigationPanePageIndex)
                {
                    return;

                }

                int oldIndex = this._activeNavigationPanePageIndex;

                NavigationPanePage oldPage = null;
                string oldKey = string.Empty;

                if (oldIndex > -1)
                {
                    oldPage = this._navigationPageCollection[oldIndex];
                    oldKey = this._navigationPageCollection[oldIndex].Key;

                }

                NavigationPaneCancelEventArgs navigationPaneCancelEventArgsDeselecting = new NavigationPaneCancelEventArgs(oldPage, oldIndex, oldKey, false, NavigationPaneAction.Deselecting);
                this.OnDeselecting(navigationPaneCancelEventArgsDeselecting);

                if (!navigationPaneCancelEventArgsDeselecting.Cancel)
                {
                    NavigationPaneCancelEventArgs navigationPaneCancelEventArgsSecting = new NavigationPaneCancelEventArgs(oldPage, oldIndex, oldKey, false, NavigationPaneAction.Selecting);
                    this.OnSelecting(navigationPaneCancelEventArgsSecting);

                    if (!navigationPaneCancelEventArgsSecting.Cancel)
                    {
                        this._activeNavigationPanePageIndex = value;

                        if ((value > -1) && (value < this._navigationPageCollection.Count) && (value < this._render.DisplayOrder.Count))
                        {
                            if (oldIndex > -1) this.OnDeselected(new NavigationPaneEventArgs(oldPage, oldIndex, oldKey, NavigationPaneAction.Deselected));

                            this._currentDisplayOrderName = this._render.DisplayOrder[value].ToString();

                            if (this._render.DisplayOrder.Contains(this._currentDisplayOrderName))
                            {
                                this._render.ActiveIndex = this._render.DisplayOrder.IndexOf(this._currentDisplayOrderName);

                            }

                            int index = this._navigationPageCollection.IndexOf(this._currentDisplayOrderName);

                            this._render.ActiveIndex = value;

                            this._navigationPageCollection[index].BringToFront();

                            base.Invalidate();

                            this.OnSelectedIndexChanged(new EventArgs());

                            this._navigationPageCollection[index].Focus();
                            this._navigationPageCollection[index].Select();

                            if (this.DesignMode)
                            {
                                this.Focus();
                                this.Select();

                            }

                            this.OnSelected(new NavigationPaneEventArgs(this._navigationPageCollection[index], index, this._navigationPageCollection[index].Key, NavigationPaneAction.Selected));

                        }

                    }

                }

            }

        }

        /// <summary>
        /// Gets or sets the split bar gradient high color on the control.
        /// </summary>
        [Browsable(false)]
        [DefaultValue(typeof(Color), "GradientActiveCaption")]
        public Color SplitBarGradientHighColor
        {
            get
            {
                return this._render.SplitBarGradientHighColor;

            }

            set
            {
                if (this._render.SplitBarGradientHighColor == value)
                {
                    return;

                }

                this._render.SplitBarGradientHighColor = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the split bar gradient low color.
        /// </summary>
        [Browsable(false)]
        [DefaultValue(typeof(Color), "ActiveCaption")]
        public Color SplitBarGradientLowColor
        {
            get
            {
                return this._render.SplitBarGradientLowColor;

            }

            set
            {
                if (this._render.SplitBarGradientLowColor == value)
                {
                    return;

                }

                this._render.SplitBarGradientLowColor = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the splitbar height on the control.
        /// </summary>
        [Browsable(false)]
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("SplitBarHeightDescription"), DefaultValueAttribute(7)]
        public int SplitBarHeight
        {
            get
            {
                return this._render.SplitBarHeight;

            }

            set
            {
                if (this._render.SplitBarHeight == value)
                {
                    return;

                }

                this._render.SplitBarHeight = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the split bar border color on the control.
        /// </summary>
        [Browsable(false)]
        [DefaultValue(typeof(Color), "ActiveCaption")]
        public Color SplitBarBorderColor
        {
            get
            {
                return this._render.SplitBarBorderColor;

            }

            set
            {
                if (this._render.SplitBarBorderColor == value)
                {
                    return;

                }

                this._render.SplitBarBorderColor = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the split bar properties.
        /// </summary>
        [DesignOnlyAttribute(true), EditorBrowsableAttribute(EditorBrowsableState.Never), ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("SplitBarDescription"), ResourceDisplayName("DisplayNameSplitBar")]
        public NavigationPaneSplitBarProperty SplitBar
        {
            get
            {
                return this._splitBarProperty;

            }

            set
            {
                this._splitBarProperty = value;

            }

        }

        /// <summary>
        /// Determines if the SplitBar property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>true or false</returns>
        public bool ShouldSerializeSplitBar()
        {
            return ((this._render.SplitBarHeight != 7) || (this._render.SplitBarGradientHighColor != SystemColors.GradientActiveCaption) || (this._render.SplitBarGradientLowColor != SystemColors.ActiveCaption) || (this._render.SplitBarBorderColor != SystemColors.ActiveCaption));

        }

        /// <summary>
        /// Resets the splitbar to default values.
        /// </summary>
        public void ResetSplitBar()
        {
            this._render.SplitBarHeight = 7;
            this._render.SplitBarGradientHighColor = SystemColors.GradientActiveCaption;
            this._render.SplitBarGradientLowColor = SystemColors.ActiveCaption;
            this._render.SplitBarBorderColor = SystemColors.ActiveCaption;

            base.Invalidate();

        }

        /// <summary>
        /// Gets or sets the text associated with this control.
        /// </summary>
        [EditorBrowsable(EditorBrowsableState.Never), Browsable(false), Bindable(false)]
        public override string Text
        {
            get
            {
                return base.Text;

            }

            set
            {
                base.Text = value;

            }

        }

        /// <summary>
        /// Gets the internal renderer.
        /// </summary>
        [EditorBrowsable(EditorBrowsableState.Never), Browsable(false), Bindable(false)]
        public NavigationPaneRender Render
        {
            get
            {
                return this._render;

            }

        }

        /// <summary>
        /// Specifies the painting style applied to the background in a control.
        /// </summary>
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("RenderModeDescription"), ResourceDisplayName("DisplayNameRenderMode"), DefaultValueAttribute(typeof(RenderMode), "Gradient")]
        public RenderMode RenderMode
        {
            get
            {
                return this._render.RenderMode;

            }

            set
            {
                if (value == this._render.RenderMode)
                {
                    return;

                }

                this._render.RenderMode = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the ImageList that contains the Images displayed on the control. 
        /// </summary>
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("ImageListDescription"), ResourceDisplayName("DisplayNameImageList"), DefaultValueAttribute(typeof(ImageList), "(none)")]
        public ImageList ImageList
        {
            get
            {
                return this._imageList;

            }

            set
            {
                if (this._imageList != value)
                {
                    this._imageList = value;

                    for (int i = 0; i < this._navigationPageCollection.Count; i++)
                    {
                        this._navigationPageCollection[i].ImageList = value;

                    }

                    base.Invalidate();

                }

            }

        }

        /// <summary>
        /// Gets or sets the ImageList that contains the small Images displayed on the control. 
        /// </summary>
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("ImageListFooterDescription"), ResourceDisplayName("DisplayNameImageListFooter"), DefaultValueAttribute(typeof(ImageList), "(none)")]
        public ImageList ImageListFooter
        {
            get
            {
                return this._imageListFooter;

            }

            set
            {
                if (this._imageListFooter != value)
                {
                    this._imageListFooter = value;

                    for (int i = 0; i < this._navigationPageCollection.Count; i++)
                    {
                        this._navigationPageCollection[i].ImageListFooter = value;

                    }

                    base.Invalidate();

                }

            }

        }

        /// <summary>
        /// Gets or sets a value indicating whether this control should redraw its surface using a secondary buffer to reduce or prevent flicker.
        /// </summary>
        [EditorBrowsable(EditorBrowsableState.Never), Browsable(false), Bindable(false)]
        protected override bool DoubleBuffered
        {
            get
            {
                return base.DoubleBuffered;

            }

            set
            {
                base.DoubleBuffered = value;

            }

        }

        /// <summary>
        /// 
        /// </summary>
        [EditorBrowsable(EditorBrowsableState.Never), Browsable(false), Bindable(false)]
        public override System.Windows.Forms.Cursor Cursor
        {
            get
            {
                return base.Cursor;

            }

            set
            {
                base.Cursor = value;

            }

        }

        /// <summary>
        /// Gets or sets if the active button image should be shown in the caption.
        /// </summary>
        [Browsable(false)]
        [ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("ImageInCaptionDescription"), ResourceDisplayName("DisplayNameImageInCaption"), DefaultValueAttribute(false)]
        public bool ImageInCaption
        {
            get
            {
                return this._render.ShowImageInCaption;

            }

            set
            {
                if (value == this._render.ShowImageInCaption)
                {
                    return;

                }

                this._render.ShowImageInCaption = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets the number of navigation pages in the navigation pane. 
        /// </summary>
        /// <value>
        /// The number of navigation pages in the navigation pane. 
        /// </value>
        [Browsable(false), DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
        public int NavigationPageCount
        {
            get
            {
                int count = 0;

                for (int i = 0; i < this._navigationPageCollection.Count; i++)
                {
                    if (this._navigationPageCollection[i].Visible) count++;

                }

                return count;

            }

        }

        /// <summary>
        /// Gets or sets the current count of the visible buttons.
        /// </summary>
        /// <remarks>
        /// Between 0 and the total number of buttons.
        /// </remarks>
        [ResourceDescriptionAttribute("VisibleButtonCountDescription"), ResourceDisplayName("DisplayNameVisibleButtonCount")]
        [SettingsBindableAttribute(true)]
        [Browsable(false)]
        public int VisibleButtonCount
        {
            get
            {
                return this._visibleButtonCount;

            }

            set
            {
                if (this._visibleButtonCount != value)
                {
                    if (value < 0) value = 0;
                    if (value > this._maxVisibleButtonCount) value = this._maxVisibleButtonCount;

                    this._visibleButtonCount = value;

                    this._render.DisplayButtonCount = this._visibleButtonCount;

                    base.Invalidate();

                    this.SizePages();

                    this.DetermineButtonMenuState();

                }

            }

        }

        /// <summary>
        /// Determines if the VisibleButtonCount property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>always true</returns>
        public bool ShouldSerializeVisibleButtonCount()
        {
            return true;

        }

        /// <summary>
        /// Gets or sets a value that determines whether to use the compatible text rendering engine (GDI+) or not (GDI). 
        /// </summary>
        /// <value>
        /// true if the compatible text rendering engine (GDI+) is used; otherwise, false. 
        /// </value>
        [ResourceCategoryAttribute("BehaviorCategory"), ResourceDescriptionAttribute("UseCompatibleTextRenderingDescription"), ResourceDisplayName("DisplayNameUseCompatibleTextRendering"), DefaultValueAttribute(false)]
        public bool UseCompatibleTextRendering
        {
            get
            {
                return this._render.UseCompatibleTextRendering;

            }

            set
            {
                if (value == this._render.UseCompatibleTextRendering)
                {
                    return;

                }

                this._render.UseCompatibleTextRendering = value;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Gets or sets the caption properties.
        /// </summary>
        [DesignOnlyAttribute(true), EditorBrowsableAttribute(EditorBrowsableState.Never), ResourceCategoryAttribute("AppearanceCategory"), ResourceDescriptionAttribute("CaptionDescription"), ResourceDisplayName("DisplayNameCaption")]
        public NavigationPaneCaptionProperty Caption
        {
            get
            {
                return this._captionProperty;

            }

            set
            {
                this._captionProperty = value;

            }

        }

		/// <summary>
		/// Gets or set the width that the NavigationPane will minimize to.
		/// </summary>
		public int MinimizedWidth
		{
			get
			{
				//TODO: This property needs Resource attributes and Designer attributes
				return this._minimizedWidth;
			}
			set
			{
				this._minimizedWidth = value;
			}
		}

		/// <summary>
		/// Determines whether or not the NavigationPane is currently minimized.
		/// </summary>
		[Bindable(false)]
		[Browsable(false)]		
		public bool IsMinimized
		{
			get
			{
				return this._isMinimized;
			}
		}

		/// <summary>
		/// Gets or sets whether or not the NavigationPane is allowed to be minimized.
		/// </summary>
		[DefaultValue(true)]
		[Bindable(false)]
		[Description("Determines whether or not the NavigationPane may be minimized")]
		public bool AllowMinimize
		{
			get
			{
				return this._allowMinimize;
			}
			set
			{
				this._allowMinimize = value;
			}
		}

        /// <summary>
        /// Determines if the Caption property has default values or not.
        /// </summary>
        /// <remarks>
        /// This method is used internally to the control and should not be called by your code.
        /// </remarks>
        /// <returns>true or false</returns>
        public bool ShouldSerializeCaption()
        {
            return ((this._render.CaptionHeight != 26) || (this._render.CaptionGradientHighColor != SystemColors.GradientActiveCaption) || (this._render.CaptionGradientLowColor != SystemColors.ActiveCaption) || (this._render.CaptionBorderColor != SystemColors.ActiveCaption) || (this._render.CaptionForeColor != SystemColors.ActiveCaptionText) || (this._render.CaptionGradientMode != LinearGradientMode.Vertical) || (this._render.CaptionImageAlign != ContentAlignment.MiddleRight) || (this._render.CaptionTextAlign != ContentAlignment.MiddleLeft) || (this._render.ShowImageInCaption != false));

        }

        /// <summary>
        /// Resets the Caption to default values.
        /// </summary>
        public void ResetCaption()
        {
            this._render.CaptionHeight = 26;
            this._render.CaptionGradientHighColor = SystemColors.GradientActiveCaption;
            this._render.CaptionGradientLowColor = SystemColors.ActiveCaption;
            this._render.CaptionBorderColor = SystemColors.ActiveCaption;
            this._render.CaptionForeColor = SystemColors.ActiveCaptionText;
            this._render.CaptionGradientMode = LinearGradientMode.Vertical;
            this._render.CaptionImageAlign = ContentAlignment.MiddleRight;
            this._render.CaptionTextAlign = ContentAlignment.MiddleLeft;
            this._render.ShowImageInCaption = false;

            base.Invalidate();

        }

        /// <summary>
        /// Initializes a new instance of the NavigationPane class.
        /// </summary>
        public NavigationPane() : base()
        {
            base.SetStyle(ControlStyles.SupportsTransparentBackColor | ControlStyles.OptimizedDoubleBuffer | ControlStyles.UserPaint | ControlStyles.AllPaintingInWmPaint | ControlStyles.Selectable, true);
            this._render = new NavigationPaneRender(this);

            this._navigationPageCollection = new NavigationPageCollection(this);

            this._footerProperty = new NavigationPaneFooterProperty(this, 30, SystemColors.ButtonHighlight, SystemColors.GradientActiveCaption, Color.White, Color.FromArgb(255, 165, 78));
            this._captionProperty = new NavigationPaneCaptionProperty(this, 26, SystemColors.GradientActiveCaption, SystemColors.ActiveCaption, LinearGradientMode.Vertical, false, new Font(this.Font.FontFamily, 12f, FontStyle.Bold), SystemColors.ActiveCaptionText, ContentAlignment.MiddleRight, ContentAlignment.MiddleLeft, SystemColors.ActiveCaption);

            this._buttonProperty = new NavigationPaneButtonProperty(this, 32, SystemColors.ButtonHighlight, SystemColors.GradientActiveCaption, SystemColors.MenuHighlight, Color.White, Color.FromArgb(255, 165, 78), Color.FromArgb(255, 225, 155), Color.FromArgb(255, 165, 78), SystemColors.ControlText, ContentAlignment.MiddleLeft);
            this._splitBarProperty = new NavigationPaneSplitBarProperty(this, 7, SystemColors.GradientActiveCaption, SystemColors.ActiveCaption, SystemColors.ActiveCaption);

            this._activeNavigationPanePageIndex = -1;

            this._toolTip = new ToolTip();
            this._toolTip.SetToolTip(this, string.Empty);

            this._displayOptionsMenuItem = true;

            this._contextMenuStrip = new System.Windows.Forms.ContextMenuStrip();
            this._contextMenuStrip.Closed += new ToolStripDropDownClosedEventHandler(this.ContextMenuStrip_Closed);

            this._showMoreButtonsToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem();
            this._showMoreButtonsToolStripMenuItem.Click += new EventHandler(this.ShowMoreButtonsToolStripMenuItem_Click);
            this._showMoreButtonsToolStripMenuItem.Enabled = false;
            this._showMoreButtonsToolStripMenuItem.ShowShortcutKeys = true;

            this._showFewerButtonsToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem();
            this._showFewerButtonsToolStripMenuItem.Click += new EventHandler(this.ShowFewerButtonsToolStripMenuItem_Click);
            this._showFewerButtonsToolStripMenuItem.Enabled = true;
            this._showFewerButtonsToolStripMenuItem.ShowShortcutKeys = true;

            this._navigationPaneOptionsToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem();
            this._navigationPaneOptionsToolStripMenuItem.Click += new EventHandler(this.NavigationPaneOptionsToolStripMenuItem_Click);
            this._navigationPaneOptionsToolStripMenuItem.Enabled = true;
            this._navigationPaneOptionsToolStripMenuItem.ShowShortcutKeys = true;

            this._addOrRemoveButtonsToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem();
            this._addOrRemoveButtonsToolStripMenuItem.ShowShortcutKeys = true;

            this._mainDivider = new ToolStripSeparator();

            this._contextMenuStrip.Items.AddRange(new System.Windows.Forms.ToolStripItem[] {
            this._showMoreButtonsToolStripMenuItem,
            this._showFewerButtonsToolStripMenuItem,
            this._addOrRemoveButtonsToolStripMenuItem,
            this._mainDivider,
            this._navigationPaneOptionsToolStripMenuItem});

            this._showMoreButtonsToolStripMenuItem.Text = ResourceText.GetLocalizedString("NPMenuShowMoreButtonsText");
            this._showMoreButtonsToolStripMenuItem.Image = TMF.AscendedThemeKit.Properties.Resources.MenuViewPanNorth.ToBitmap();
            this._showFewerButtonsToolStripMenuItem.Text = ResourceText.GetLocalizedString("NPMenuShowFewerButtonsText");
            this._showFewerButtonsToolStripMenuItem.Image = TMF.AscendedThemeKit.Properties.Resources.MenuViewPanSouth.ToBitmap();
            this._navigationPaneOptionsToolStripMenuItem.Text = ResourceText.GetLocalizedString("NPMenuOptionsText");
            this._addOrRemoveButtonsToolStripMenuItem.Text = ResourceText.GetLocalizedString("NPMenuAddRemoveButtonsText");

            this._render.CaptionFont = new Font(this.Font.FontFamily, this.CaptionFont.Size, this.CaptionFont.Style);
            this._render.ButtonFont = new Font(this.Font.FontFamily, this.ButtonFont.Size, this.ButtonFont.Style);

        }

        /// <summary>
        /// Clears all pages and settings from the control.
        /// </summary>
        /// <remarks>
        /// This method is used internally and cannot be called by your code.
        /// </remarks>
        internal void ClearPages()
        {
            this.Controls.Clear();
            this.VisibleButtonCount = 0;
            this._maxVisibleButtonCount = 0;
            this.Render.DisplayOrder.Clear();
            this.SelectedIndex = -1;

        }

        /// <summary>
        /// Raises the Paint event.
        /// </summary>
        /// <param name="e">A System.Windows.Forms.PaintEventArgs that contains the event data.</param>
        /// <remarks>
        /// <para>
        /// Raising an event invokes the event handler through a delegate. For more information, Raising an Event.
        /// </para>
        /// <para>
        /// The OnPaint method also allows derived classes to handle the event without attaching a delegate. This is the preferred technique for handling the event in a derived class.
        /// </para>
        /// <para>
        /// Note for Inheritors:
        /// When overriding OnPaint in a derived class, be sure to call the base class's OnPaint method so that registered delegates receive the event.
        /// </para>
        /// </remarks>
        protected override void OnPaint(System.Windows.Forms.PaintEventArgs e)
        {
            if (!this.Disposing)
            {
                if (this._initialPaint)
                {
                    this._initialPaint = false;

                    this.SizePages();

                }

                base.OnPaint(e);

                if (this._render.DisplayOrder.Count >= 1 && String.IsNullOrEmpty(this._render.DisplayOrder[0].ToString()))
                {
                    this.Reset();

                }

                if (this._activeNavigationPanePageIndex == -1)
                {
                    if (this._navigationPageCollection.Count > 0)
                    {
                        this._activeNavigationPanePageIndex = 0;
                        this._navigationPageCollection[0].BringToFront();

                    }

                }

                Rectangle modifiedRectangle = new Rectangle(0, 0, (this.Width - 1), (this.Height - 1));
                this._render.DisplayRectangle = modifiedRectangle;

                this._render.Render(e);

            }

        }

        /// <summary>
        /// Fires the event indicating that the control Border has changed.  Inheriting controls should use this in favour of actually listening to the event, but should not forget to call base.OnBorderChanged() to ensure that the event is still fired for external listeners.
        /// </summary>
        /// <param name="e">A System.EventArgs that contains the event data.</param>
        protected void OnBorderChanged(EventArgs e)
        {
            if (this.BorderChanged != null)
            {
                this.BorderChanged(this, e);

            }

        }

        /// <summary>
        /// Fires the event indicating that the control BorderColor has changed.  Inheriting controls should use this in favour of actually listening to the event, but should not forget to call base.OnBorderColorChanged() to ensure that the event is still fired for external listeners.
        /// </summary>
        /// <param name="e">A System.EventArgs that contains the event data.</param>
        protected void OnBorderColorChanged(EventArgs e)
        {
            if (this.BorderColorChanged != null)
            {
                this.BorderColorChanged(this, e);

            }

        }

        /// <summary>
        /// Fires the event indicating that the control antialias has changed.  Inheriting controls should use this in favour of actually listening to the event, but should not forget to call base.OnAntiAliasChanged() to ensure that the event is still fired for external listeners.
        /// </summary>
        /// <param name="e">A System.EventArgs that contains the event data.</param>
        protected void OnAntiAliasChanged(EventArgs e)
        {
            if (this.AntiAliasChanged != null)
            {
                this.AntiAliasChanged(this, e);

            }

        }

        /// <param name="e">A System.Windows.Forms.MouseEventArgs that contains the event data.</param>
        protected override void OnMouseMove(System.Windows.Forms.MouseEventArgs e)
        {
            try
            {
                if (this._render.SplitBarRectangle != null)
                {
                    if (this._mouseDown)
                    {
                        this.Cursor = Cursors.SizeNS;

                        if (!this._blockMouseMove)
                        {
                            this._blockMouseMove = true;
                            try
                            {
                                if ((this._visibleButtonCount > 0) && e.Y >= (this.NavigationPageRectangle.Bottom + this.Render.ButtonHeight))
                                {
                                    this.LessButtons();

                                }
                                else if ((this._visibleButtonCount < this._maxVisibleButtonCount) && e.Y <= (this.NavigationPageRectangle.Bottom - this.Render.ButtonHeight))
                                {
                                    this.MoreButtons();

                                }

                            }
                            catch
                            {
                                throw;

                            }
                            finally
                            {
                                this._blockMouseMove = false;

                            }

                        }

                        this._toolTip.SetToolTip(this, string.Empty);

                        return;

                    }
                    else
                    {
                        if (this._render.SplitBarRectangle.Contains(e.X, e.Y))
                        {
                            this.Cursor = Cursors.SizeNS;

                            if (this._render.HighlightIndex != -1)
                            {
                                this._render.HighlightIndex = -1;
                                this._render.ConfigureFooterHighlight = false;

                                base.Invalidate();

                            }

                            this._toolTip.SetToolTip(this, string.Empty);

                            return;

                        }
                        else
                        {
                            int buttonIndex = -1;

                            for (int i = 0; i < this._navigationPageCollection.Count; i++)
                            {
                                if (this._navigationPageCollection[i].ButtonRectangle.Contains(e.X, e.Y))
                                {
                                    if (this._render.DisplayOrder.Contains(this._navigationPageCollection[i].Name))
                                    {
                                        buttonIndex = this._render.DisplayOrder.IndexOf(this._navigationPageCollection[i].Name);

                                    }

                                    if (this._render.HighlightIndex != buttonIndex)
                                    {
                                        if (this._navigationPageCollection[i].Enabled)
                                        {
                                            this.Cursor = Cursors.Hand;

                                        }
                                        else
                                        {
                                            this.Cursor = Cursors.No;

                                        }

                                        this._render.HighlightIndex = buttonIndex;
                                        this._render.ConfigureFooterHighlight = false;

                                        if (this._navigationPageCollection[i].ButtonMinimized)
                                        {
                                            if (String.IsNullOrEmpty(this._navigationPageCollection[i].ToolTipText))
                                            {
                                                this._toolTip.SetToolTip(this, this._navigationPageCollection[i].Text);

                                            }
                                            else
                                            {
                                                this._toolTip.SetToolTip(this, this._navigationPageCollection[i].ToolTipText);

                                            }


                                        }
                                        else
                                        {
                                            this._toolTip.SetToolTip(this, string.Empty);

                                        }

                                        base.Invalidate();

                                    }

                                    return;

                                }

                            }

                            if (this._render.FooterConfigureRectangle.Contains(e.X, e.Y))
                            {
                                if (!this._render.ConfigureFooterHighlight)
                                {
                                    this._render.HighlightIndex = -1;
                                    this._render.ConfigureFooterHighlight = true;

                                    this.Cursor = Cursors.Hand;

                                    base.Invalidate();

                                    this._toolTip.SetToolTip(this, ResourceText.GetLocalizedString("ConfigureButtonsToolTipText"));

                                }

                                return;

                            }
                            else
                            {
                                if ((this._render.HighlightIndex != -1) || this._render.ConfigureFooterHighlight)
                                {
                                    this._render.HighlightIndex = -1;
                                    this._render.ConfigureFooterHighlight = false;

                                    this.Cursor = Cursors.Default;

                                    this._toolTip.SetToolTip(this, string.Empty);

                                    base.Invalidate();

                                    return;

                                }
                                else
                                {
                                    this.Cursor = Cursors.Default;

                                    this._toolTip.SetToolTip(this, string.Empty);

                                    return;

                                }

                            }

                        }

                    }

                }

            }
            catch
            {
                throw;

            }
            finally
            {
                base.OnMouseMove(e);

            }

        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="page">The navigationPanePage that is being added.</param>
        internal void PageAdded(NavigationPanePage page)
        {
            if (!this.Controls.Contains(page))
            {
                this.Controls.Add(page);
                page.ImageIndexChanged += new EventHandler(this.OnPageChanged);
                page.TextChanged += new EventHandler(this.OnPageChanged);
                page.ImageList = this._imageList;
                page.ImageListFooter = this._imageListFooter;
                page.ButtonFont = this.ButtonFont;

            }

            if (page.ButtonVisible)
            {
                this._visibleButtonCount++;
                this._maxVisibleButtonCount++;

                this._render.DisplayButtonCount = this._visibleButtonCount;

            }

            if (!DesignMode)
            {
                this._render.DisplayOrder.Add(page.Name);

            }
            else
            {
                if (string.IsNullOrEmpty(page.Text))
                {
                    page.Text = page.Name;

                }

                if (!this._render.DisplayOrder.Contains(page.Name))
                {
                    this._render.DisplayOrder.Add(page.Name);

                }
                else
                {
                    int index = this._render.DisplayOrder.IndexOf(page.Name);

                    if (index > -1) this._render.DisplayOrder.RemoveAt(index);

                    this._render.DisplayOrder.Add(page.Name);

                }

            }

            base.Invalidate();

        }

        /// <summary>
        /// Sizes the navigation pages to the available space.
        /// </summary>
        private void SizePages()
        {
            if (this.Visible)
            {
                this.SizePages(this.NavigationPageRectangle);

            }

        }

        /// <summary>
        /// Sizes the navigation pages to the available space.
        /// </summary>
        /// <param name="rectangle">The bounds of the navigation pane page</param>
        private void SizePages(Rectangle rectangle)
        {
            if (this.Visible)
            {
                for (int i = 0; i < this._navigationPageCollection.Count; i++)
                {
                    this._navigationPageCollection[i].Bounds = rectangle;

                }

            }

        }

        ///<summary>
        /// Raises the MouseLeave event.
        /// </summary>
        /// <param name="e">An System.EventArgs that contains the event data.</param>
        protected override void OnMouseLeave(System.EventArgs e)
        {
            base.OnMouseLeave(e);

            this.Cursor = Cursors.Default;

            if (this._render.HighlightIndex != -1)
            {
                this._render.HighlightIndex = -1;
                this._render.ConfigureFooterHighlight = false;

                base.Invalidate();

            }

        }

        /// <summary>
        /// Raises the MouseClick event.
        /// </summary>
        /// <param name="e">An System.EventArgs that contains the event data.</param>
        protected override void OnMouseClick(System.Windows.Forms.MouseEventArgs e)
        {
            base.OnMouseClick(e);

            if (!this._mouseDown && e.Button == MouseButtons.Left)
            {
                int actualIndex = 0;

                for (int i = 0; i < this._navigationPageCollection.Count; i++)
                {
                    if (this._navigationPageCollection[i].ButtonRectangle.Contains(e.X, e.Y))
                    {
                        if (this._navigationPageCollection[i].Enabled)
                        {
                            this.SelectedNavigationPage = this._navigationPageCollection[i];

                        }
                        break;

                    }

                    actualIndex++;

                }

                if (this._render.FooterConfigureRectangle.Contains(e.X, e.Y))
                {
                    this.DetermineButtonMenuState();
                    this._contextMenuStrip.Show(this, (this._render.FooterConfigureRectangle.Left + this._render.FooterConfigureRectangle.Width), (this._render.FooterConfigureRectangle.Top + (this._render.FooterRectangle.Height / 2)));

                }

            }

        }

        /// <summary>
        /// Raises the Resize event. 
        /// </summary>
        /// <param name="e">An System.EventArgs that contains the event data.</param>
        protected override void OnResize(System.EventArgs e)
        {
            base.OnResize(e);

            base.Invalidate();

            this.SizePages();

        }

        /// <summary>
        /// Raises the Selecting event.
        /// </summary>
        /// <param name="e">A NavigationPaneCancelEventArgs that contains the event data.</param>
        /// <remarks>
        /// Raising an event invokes the event handler through a delegate.
        /// The OnSelecting method also enables derived classes to handle the event without attaching a delegate. This is the preferred technique for handling the event in a derived class.
        /// Notes to Inheritors When overriding OnSelecting in a derived class, be sure to call the base class's OnSelecting method so that registered delegates receive the event. 
        /// </remarks>
        protected virtual void OnSelecting(NavigationPaneCancelEventArgs e)
        {
            if (this.Selecting != null)
            {
                this.Selecting(this, e);

            }

        }

        /// <summary>
        /// Raises the Selected event.
        /// </summary>
        /// <param name="e">A NavigationPaneEventArgs that contains the event data.</param>
        protected virtual void OnSelected(NavigationPaneEventArgs e)
        {
            if (this.Selected != null)
            {
                this.Selected(this, e);

            }

        }

        /// <summary>
        /// Raises the SelectedIndexChanged event.
        /// </summary>
        /// <param name="e">An System.EventArgs that contains the event data.</param>
        private void OnSelectedIndexChanged(EventArgs e)
        {
            if (this.SelectedIndexChanged != null)
            {
                this.SelectedIndexChanged(this, e);

            }

        }

        /// <summary>
        /// Called when a page is removed by an external class.
        /// </summary>
        /// <param name="page">The NavigationPanePage the is being removed.</param>
        internal void PageRemoved(NavigationPanePage page)
        {
            page.ImageIndexChanged -= new EventHandler(this.OnPageChanged);
            page.TextChanged -= new EventHandler(this.OnPageChanged);

            if ((this._activeNavigationPanePageIndex >= (this._navigationPageCollection.Count - 1)) && (this._navigationPageCollection.Count > 0))
            {
                this._activeNavigationPanePageIndex = 0;

            }

            if (page.ButtonVisible)
            {
                this._maxVisibleButtonCount--;
                this.VisibleButtonCount = (this.VisibleButtonCount - 1);

                this._render.DisplayButtonCount = this._visibleButtonCount;

            }

            if (this._render.DisplayOrder.Contains(page.Name)) this._render.DisplayOrder.Remove(page.Name);
            this._render.DisplayButtonCount = this._visibleButtonCount;

            if (!this.DesignMode)
            {
                if (this.Controls.Contains(page))
                {
                    this.Controls.Remove(page);

                }

            }

            base.Invalidate();

        }

        private void ContextMenuStrip_Closed(object sender, ToolStripDropDownClosedEventArgs e)
        {
            this._render.ConfigureFooterHighlight = false;

        }

        /// <param name="e">A System.Windows.Forms.MouseEventArgs that contains the event data.</param>
        protected override void OnMouseDown(System.Windows.Forms.MouseEventArgs e)
        {
            if (this._render.SplitBarRectangle.Contains(e.X, e.Y))
            {
                if (e.Button == MouseButtons.Left)
                {
                    this._mouseDown = true;

                }

            }

        }

        /// <param name="e">A System.Windows.Forms.MouseEventArgs that contains the event data.</param>
        protected override void OnMouseUp(System.Windows.Forms.MouseEventArgs e)
        {
            this._mouseDown = false;

        }

        /// <summary>
        /// Shows less buttons on the navigaiton pane.
        /// </summary>
        public void LessButtons()
        {
            if (this._visibleButtonCount > 0)
            {
                this.VisibleButtonCount = (this._visibleButtonCount - 1);

            }

        }

        /// <summary>
        /// Shows more buttons on the navigation pane.
        /// </summary>
        public void MoreButtons()
        {
            if (this._visibleButtonCount < this._maxVisibleButtonCount)
            {
                this.VisibleButtonCount = (this._visibleButtonCount + 1);

            }

        }

        /// <summary>
        /// Makes the NavigationPage following the NavigationPage with the specified key the current NavigationPage. 
        /// </summary>
        /// <param name="key">The key in the NavigationPages collection of the NavigationPage to deselect.</param>
        /// <remarks>
        /// Use this method to programmatically deselect a particular NavigationPage in a NavigationPane. If there are at least two NavigationPages in the control, the NavigationPage following the specified NavigationPage becomes the current NavigationPage. If the specified NavigationPage is the last NavigationPage in the control, the first NavigationPage becomes the current NavigationPage.
        /// </remarks>
        public void DeselectNavigationPage(string key)
        {
            int pageIndex = this._navigationPageCollection.IndexOf(key);

            if (pageIndex != -1)
            {
                this.DeselectNavigationPage(pageIndex);

            }

        }


        /// <summary>
        /// Makes the NavigationPage following the specified NavigationPage as the current NavigationPage. 
        /// </summary>
        /// <param name="page">The NavigationPage to be deselected from NavigationPages collection</param>
        /// <remarks>
        /// Use this method to programmatically deselect a particular NavigationPage in a NavigationPane. If there are at least two NavigationPages in the control, the NavigationPage following the specified NavigationPage becomes the current NavigationPage. If the specified NavigationPage is the last NavigationPage in the control, the first NavigationPage becomes the current NavigationPage.
        /// </remarks>       
        public void DeselectNavigationPage(NavigationPanePage page)
        {
            int pageIndex = this._navigationPageCollection.IndexOf(page);

            if (pageIndex != -1)
            {
                this.DeselectNavigationPage(pageIndex);
            }

        }

        /// <summary>
        /// Makes the NavigationPage following the NavigationPage with the specified index the current NavigationPage. 
        /// </summary>
        /// <param name="index">The index in the NavigationPages collection of the NavigationPage to deselect.</param>
        /// <remarks>
        /// Use this method to programmatically deselect a particular NavigationPage in a NavigationPane. If there are at least two NavigationPages in the control, the NavigationPage following the specified NavigationPage becomes the current NavigationPage. If the specified NavigationPage is the last NavigationPage in the control, the first NavigationPage becomes the current NavigationPage.
        /// </remarks>
        public void DeselectNavigationPage(int index)
        {

            NavigationPanePage navigationPanePage = this.GetNavigationPanePage(index);

            if (this.SelectedNavigationPage == navigationPanePage)
            {
                if ((0 <= index) && (index < (this.NavigationPages.Count - 1)))
                {
                    this.SelectedIndex = ++index;

                }
                else
                {
                    this.SelectedIndex = 0;

                }

            }

        }

        private void DetermineButtonMenuState()
        {
            if (!this.DesignMode)
            {
                if (this._maxVisibleButtonCount != 0)
                {
                    if (this._visibleButtonCount == this._maxVisibleButtonCount)
                    {
                        this._showMoreButtonsToolStripMenuItem.Enabled = false;

                    }
                    else
                    {
                        this._showMoreButtonsToolStripMenuItem.Enabled = true;

                    }

                    if (this._visibleButtonCount == 0)
                    {
                        this._showFewerButtonsToolStripMenuItem.Enabled = false;

                    }
                    else
                    {
                        this._showFewerButtonsToolStripMenuItem.Enabled = true;

                    }

                }
                else
                {
                    this._showMoreButtonsToolStripMenuItem.Enabled = false;
                    this._showFewerButtonsToolStripMenuItem.Enabled = false;

                }

                if ((this._navigationPageCollection != null) && (this._navigationPageCollection.Count > 0))
                {
                    this._navigationPaneOptionsToolStripMenuItem.Enabled = true;
                    this._addOrRemoveButtonsToolStripMenuItem.Enabled = true;

                    if (this._displayOptionsMenuItem)
                    {
                        this._mainDivider.Visible = true;
                        this._navigationPaneOptionsToolStripMenuItem.Visible = true;

                    }
                    else
                    {
                        this._mainDivider.Visible = false;
                        this._navigationPaneOptionsToolStripMenuItem.Visible = false;

                    }

                    if ((this._navigationPageCollection.Count != this._addOrRemoveButtonsToolStripMenuItem.DropDownItems.Count) || this._resetDisplayOrder)
                    {
                        this._resetDisplayOrder = false;

                        if (this._addOrRemoveButtonsToolStripMenuItem.HasDropDownItems) this._addOrRemoveButtonsToolStripMenuItem.DropDownItems.Clear();

                        for (int i = 0; i < this._contextMenuStrip.Items.Count; i++)
                        {
                            string name = this._contextMenuStrip.Items[i].Name;

                            if ((name != this._addOrRemoveButtonsToolStripMenuItem.Name) && (name != this._showMoreButtonsToolStripMenuItem.Name) && (name != this._showFewerButtonsToolStripMenuItem.Name) && (name != this._navigationPaneOptionsToolStripMenuItem.Name) && (name != this._mainDivider.Name))
                            {
                                this._contextMenuStrip.Items.Remove(this._contextMenuStrip.Items[i]);

                            }

                        }

                        ToolStripMenuItem buttonMenuItem;
                        ToolStripMenuItem buttonMenuItemMinimized;
                        int index;

                        for (int i = 0; i < this._render.DisplayOrder.Count; i++)
                        {
                            index = this._navigationPageCollection.IndexOf(this._render.DisplayOrder[i].ToString());

                            if (index > -1)
                            {
                                buttonMenuItem = new ToolStripMenuItem(this._navigationPageCollection[index].Text, this._navigationPageCollection[index].Image, this.AddRemoveMenuItem_Click);

                                if (this._navigationPageCollection[index].Visible)
                                {
                                    buttonMenuItem.Checked = true;

                                }

                                this._addOrRemoveButtonsToolStripMenuItem.DropDownItems.Add(buttonMenuItem);

                                buttonMenuItemMinimized = new ToolStripMenuItem(this._navigationPageCollection[index].Text, this._navigationPageCollection[index].Image, this.MinimizedMenuItem_Click, "MenuItemMinimized" + this._navigationPageCollection[index].Text);
                                buttonMenuItemMinimized.Visible = false;
                                buttonMenuItemMinimized.Checked = false;
                                buttonMenuItemMinimized.Tag = this._render.DisplayOrder[i].ToString();

                                this._contextMenuStrip.Items.Add(buttonMenuItemMinimized);

                            }

                        }

                    }
                    else
                    {
                        int index;

                        for (int i = 0; i < this._render.DisplayOrder.Count; i++)
                        {
                            index = this._navigationPageCollection.IndexOf(this._render.DisplayOrder[i].ToString());

                            if (index > -1)
                            {
                                this._addOrRemoveButtonsToolStripMenuItem.DropDownItems[i].Text = this._navigationPageCollection[index].Text;

                                if (this._navigationPageCollection[index].ButtonVisible)
                                {
                                    ((ToolStripMenuItem)this._addOrRemoveButtonsToolStripMenuItem.DropDownItems[i]).Checked = true;

                                }
                                else
                                {
                                    ((ToolStripMenuItem)this._addOrRemoveButtonsToolStripMenuItem.DropDownItems[i]).Checked = false;

                                }

                                ((ToolStripMenuItem)this._addOrRemoveButtonsToolStripMenuItem.DropDownItems[i]).Visible = this._navigationPageCollection[index].Visible;

                            }

                        }

                    }

                    int indexMinimized;
                    ToolStripItem minimizedItem;

                    for (int i = 0; i < this._render.DisplayOrder.Count; i++)
                    {
                        indexMinimized = this._navigationPageCollection.IndexOf(this._render.DisplayOrder[i].ToString());

                        if (indexMinimized > -1)
                        {
                            minimizedItem = this._contextMenuStrip.Items["MenuItemMinimized" + this._navigationPageCollection[indexMinimized].Text];

                            ToolStripMenuItem toolStripMenuItem = minimizedItem as ToolStripMenuItem;

                            if (toolStripMenuItem != null)
                            {
                                if (!this._navigationPageCollection[indexMinimized].ButtonMinimizedVisible)
                                {
                                    this._mainDivider.Visible = true;
                                    minimizedItem.Visible = true;

                                    if (toolStripMenuItem != null)
                                    {
                                        if (i == this._activeNavigationPanePageIndex)
                                        {
                                            toolStripMenuItem.Checked = true;

                                        }
                                        else
                                        {
                                            toolStripMenuItem.Checked = false;

                                        }

                                    }

                                }
                                else
                                {
                                    minimizedItem.Visible = false;

                                    if (toolStripMenuItem != null)
                                    {
                                        toolStripMenuItem.Checked = false;

                                    }

                                }

                            }

                        }

                    }

                }
                else
                {
                    this._navigationPaneOptionsToolStripMenuItem.Enabled = false;
                    this._addOrRemoveButtonsToolStripMenuItem.Enabled = false;
                    this._mainDivider.Visible = false;

                }

            }

        }

        private void ShowMoreButtonsToolStripMenuItem_Click(object sender, EventArgs e)
        {
            this.MoreButtons();

        }

        private void ShowFewerButtonsToolStripMenuItem_Click(object sender, EventArgs e)
        {
            this.LessButtons();

        }

        private void MinimizedMenuItem_Click(object sender, EventArgs e)
        {
            int index;

            index = this._render.DisplayOrder.IndexOf(((ToolStripMenuItem)sender).Tag.ToString());

            this.SelectedIndex = index;

        }

        private void AddRemoveMenuItem_Click(object sender, EventArgs e)
        {
            ToolStripMenuItem toolStripMenuItem = sender as ToolStripMenuItem;

            toolStripMenuItem.Checked = !toolStripMenuItem.Checked;

            NavigationPanePage navigationPanePage = this.FindPage(toolStripMenuItem.Text);

            if (navigationPanePage != null)
            {
                if (navigationPanePage.ButtonVisible != toolStripMenuItem.Checked)
                {
                    if (toolStripMenuItem.Checked)
                    {
                        this.ShowButton(navigationPanePage.Key);

                    }
                    else
                    {
                        this.HideButton(navigationPanePage.Key);

                    }

                    base.Invalidate();

                }

            }

        }

        private void NavigationPaneOptionsToolStripMenuItem_Click(object sender, EventArgs e)
        {
            NavigationPaneOptions navigationPaneOptions = new NavigationPaneOptions();
            try
            {
                navigationPaneOptions.ParentNavigationPane = this;
                navigationPaneOptions.Font = this.Font;
                navigationPaneOptions.BuildDisplayOrder(this._render.DisplayOrder);


                DialogResult dialogResult = navigationPaneOptions.ShowDialog();

                if (dialogResult == DialogResult.OK)
                {
                    if (navigationPaneOptions.HasChanges)
                    {
                        if (this._navigationPageCollection != null && this._navigationPageCollection.Count > 0)
                        {
                            this._render.DisplayOrder.Clear();
                            this._render.DisplayOrder.AddRange(navigationPaneOptions.DisplayOrder);

                            int newIndex;

                            if (!string.IsNullOrEmpty(this._currentDisplayOrderName))
                            {
                                newIndex = this._render.DisplayOrder.IndexOf(this._currentDisplayOrderName);

                            }
                            else
                            {
                                newIndex = this._render.DisplayOrder.IndexOf(this._navigationPageCollection[0].Name);

                            }

                            if (this.SelectedIndex != newIndex)
                            {
                                this.SelectedIndex = newIndex;

                            }
                            else
                            {
                                base.Invalidate();

                            }

                        }

                    }

                }

            }
            catch
            {
                throw;

            }
            finally
            {
                navigationPaneOptions.Dispose();

            }

        }

        private NavigationPanePage FindPage(string text)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].Text == text)
                {
                    return this._navigationPageCollection[i];

                }

            }

            return null;

        }

        private NavigationPanePage GetNavigationPanePage(int index)
        {
            if ((index < 0) || (index >= this.NavigationPageCount))
            {
                throw new ArgumentOutOfRangeException("index");

            }

            return this._navigationPageCollection[index];

        }


        private void OnPageChanged(object sender, EventArgs e)
        {
            base.Invalidate();

        }

        /// <summary>
        /// Releases the unmanaged resources used by the NavigationPane and optionally releases the managed resources.
        /// </summary>
        /// <param name="disposing">true to release both managed and unmanaged resources; false to release only unmanaged resources.</param>
        protected override void Dispose(bool disposing)
        {
            try
            {
                if (!this._disposed)
                {
                    if (disposing)
                    {
                        if (this._render != null) this._render.Dispose();
                        if (this._imageList != null) this._imageList = null;
                        if (this._imageListFooter != null) this._imageListFooter = null;

                    }

                }

                this._disposed = true;

            }
            catch
            {
                throw;

            }
            finally
            {
                base.Dispose(disposing);

            }

        }

        /// <summary>
        /// Raises the ControlAdded event.
        /// </summary>
        /// <param name="e">A System.Windows.Forms.ControlEventArgs that contains the event data.</param>
        protected override void OnControlAdded(System.Windows.Forms.ControlEventArgs e)
        {
            base.OnControlAdded(e);

            if (e.Control is NavigationPanePage)
            {
                NavigationPanePage page = e.Control as NavigationPanePage;

                if (page != null)
                {
                    Rectangle rectangle = this.NavigationPageRectangle;
                    rectangle.Height = (rectangle.Height - this.ButtonHeight);

                    page.Bounds = rectangle;

                    this.SizePages(rectangle);

                    page.Focus();

                }

            }

        }

        /// <summary>
        /// Raises the Deselected event.
        /// </summary>
        /// <param name="e">A NavigationPaneEventArgs that contains the event data.</param>
        /// <remarks>
        /// Raising an event invokes the event handler through a delegate. For more information, see Raising an Event.
        /// The OnDeselected method also enables derived classes to handle the event without attaching a delegate. This is the preferred technique for handling the event in a derived class.
        /// Notes to Inheritors When overriding OnDeselected in a derived class, be sure to call the base class's OnDeselected method so that registered delegates receive the event. 
        /// </remarks>
        protected virtual void OnDeselected(NavigationPaneEventArgs e)
        {
            if (this.Deselected != null)
            {
                this.Deselected(this, e);

            }

        }

        /// <summary>
        /// Raises the Deselecting event.
        /// </summary>
        /// <param name="e">A NavigationPaneCancelEventArgs that contains the event data.</param>
        /// <remarks>
        /// Raising an event invokes the event handler through a delegate.
        /// The OnSelecting method also enables derived classes to handle the event without attaching a delegate. This is the preferred technique for handling the event in a derived class.
        /// Notes to Inheritors When overriding OnSelecting in a derived class, be sure to call the base class's OnDeselecting method so that registered delegates receive the event. 
        /// </remarks>
        protected virtual void OnDeselecting(NavigationPaneCancelEventArgs e)
        {
            if (this.Deselecting != null)
            {
                this.Deselecting(this, e);

            }

        }

        /// <summary>
        /// Raises the SystemColorsChanged event.
        /// </summary>
        /// <param name="e">An <see cref="T:System.EventArgs"></see> that contains the event data.</param>
        protected override void OnSystemColorsChanged(System.EventArgs e)
        {
            this._render.ResetColors();

            base.OnSystemColorsChanged(e);

        }

        /// <summary>
        /// Returns a String containing information about the control.
        /// </summary>
        /// <returns>A <see cref="T:System.String"></see> containing the name of the <see cref="T:System.ComponentModel.Component"></see>, if any, or null if the <see cref="T:System.ComponentModel.Component"></see> is unnamed.</returns>
        public override string ToString()
        {
            StringBuilder returnString = new StringBuilder(base.ToString());

            if (this.NavigationPages != null)
            {
                returnString.Append(", NavigationPages.Count: " + this.NavigationPages.Count.ToString(CultureInfo.CurrentCulture));

                if (this.NavigationPages.Count > 0)
                {
                    returnString.Append(", NavigationPages[0]: " + this.NavigationPages[0].ToString());

                }

            }

            return returnString.ToString();

        }

        /// <summary>
        /// Resets any user customization to original design.
        /// </summary>
        public void Reset()
        {
            this._render.DisplayOrder.Clear();

            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                this._render.DisplayOrder.Add(this._navigationPageCollection[i].Name);
                if (this._navigationPageCollection[i].Visible) this._navigationPageCollection[i].ButtonVisible = true;

            }

            base.Invalidate();

        }

        /// <summary>
        /// Makes the navigation page with the specified index the current navigation page.
        /// </summary>
        /// <remarks>Use this method to programmatically select a particular navigation page in a Navigation pane.</remarks>
        /// <param name="index">The index in the NavigationPages collection of the navigaiton page to select.</param>
        public void SelectNavigationPage(int index)
        {
            this.SelectedIndex = index;

        }

        /// <summary>
        /// Makes the navigation page with the specified key the current navigation page.
        /// </summary>
        /// <remarks>Use this method to programmatically select a particular navigation page in a Navigation pane.</remarks>
        /// <param name="key">The key in the NavigationPages collection of the navigaiton page to select.</param>
        public void SelectNavigationPage(string key)
        {
            int index = -1;

            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].Key == key)
                {
                    index = this._render.DisplayOrder.IndexOf(this._navigationPageCollection[i].Name);
                    break;

                }

            }

            if (index > -1) this.SelectedIndex = index;

        }

        /// <summary>
        /// Makes the navigation page the current navigation page.
        /// </summary>
        /// <remarks>Use this method to programmatically select a particular navigation page in a Navigation pane.</remarks>
        /// <param name="page">The NavigationPanePage in the NavigationPages collection to select.</param>
        public void SelectNavigationPage(NavigationPanePage page)
        {
            if (page == null)
            {
                throw new ArgumentNullException("page");

            }

            this.SelectNavigationPage(page.Key);

        }

        /// <summary>
        /// Disables the navigation page with the specified key.
        /// </summary>
        /// <remarks>Use this method to programmatically disable a particular navigation page in a Navigation pane.</remarks>
        /// <param name="key">The key in the NavigationPages collection of the navigaiton page to disable.</param>
        public void DisableNavigationPage(string key)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].Key == key)
                {
                    this._navigationPageCollection[i].Enabled = false;
                    break;

                }

            }

        }

        /// <summary>
        /// Enables the navigation page with the specified key.
        /// </summary>
        /// <remarks>Use this method to programmatically enable a particular navigation page in a Navigation pane.</remarks>
        /// <param name="key">The key in the NavigationPages collection of the navigaiton page to enable.</param>
        public void EnableNavigationPage(string key)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].Key == key)
                {
                    this._navigationPageCollection[i].Enabled = true;
                    break;

                }

            }

        }

        /// <summary>
        /// Shows the button with the specified key.
        /// </summary>
        /// <param name="key">The key in the NavigationPages collection of the navigaiton page to show.</param>
        public void ShowButton(string key)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].Key == key)
                {
                    if (!this._navigationPageCollection[i].ButtonVisible)
                    {
                        this._navigationPageCollection[i].ButtonVisible = true;
                        this.VisibleButtonCount++;
                        this._maxVisibleButtonCount++;

                        base.Invalidate();

                        this.DetermineButtonMenuState();

                    }

                    break;

                }

            }

        }

        /// <summary>
        /// Hides the button with the specified key.
        /// </summary>
        /// <param name="key">The key in the NavigationPages collection of the navigaiton page to hide.</param>
        public void HideButton(string key)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].Key == key)
                {
                    if (this._navigationPageCollection[i].ButtonVisible && this._navigationPageCollection[i].Visible)
                    {
                        this._navigationPageCollection[i].ButtonVisible = false;
                        this.VisibleButtonCount--;
                        this._maxVisibleButtonCount--;

                        base.Invalidate();

                        this.DetermineButtonMenuState();

                    }
                    break;

                }

            }

        }

		/// <summary>
		/// Minimizes the NavigationPane if the AllowMinimize property is true.
		/// </summary>
		public void Minimize()
		{
			if (this.AllowMinimize)
			{
				this.Size = MinimumSize;
				this._isMinimized = true;
				
				// Throw the Minimized event
				if (this.Minimized != null)
				{
					Minimized(this, new EventArgs());
				}
			}
		}

		/// <summary>
		/// Maximizes the NavigationPane.
		/// </summary>
		public void Maximize()
		{
			this.Size = MaximumSize;
			this._isMinimized = false;

			// Throw the Maximized event
			if (this.Maximized != null)
			{
				Maximized(this, new EventArgs());
			}
		}

        private void SetFontFamily(Font newFont)
        {
            if ((this.CaptionFont == null) || (this.CaptionFont.Name == this._initialFontName))
            {
                this.CaptionFont = new Font(newFont.FontFamily, this.CaptionFont.Size, this.CaptionFont.Style);

            }

            if ((this.ButtonFont == null) || (this.ButtonFont.Name == this._initialFontName))
            {
                this.ButtonFont = new Font(newFont.FontFamily, this.ButtonFont.Size, this.ButtonFont.Style);

            }

            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].ButtonFont.Name == this._initialFontName)
                {
                    this._navigationPageCollection[i].ButtonFont = new Font(newFont.FontFamily, this._navigationPageCollection[i].ButtonFont.Size, this._navigationPageCollection[i].ButtonFont.Style);

                }

            }

        }

        /// <summary>
        /// Raises the RightToLeftChanged event. 
        /// </summary>
        /// <param name="e">An System.EventArgs that contains the event data.</param>
        protected override void OnRightToLeftChanged(System.EventArgs e)
        {
            base.OnRightToLeftChanged(e);

            if (this.RightToLeft == RightToLeft.Yes)
            {
                this._render.RightToLeft = true;

            }
            else
            {
                this._render.RightToLeft = false;

            }

        }

        /// <param name="e">An <see cref="T:System.EventArgs"></see> that contains the event data.</param>
        protected override void OnFontChanged(System.EventArgs e)
        {
            this.SetFontFamily(this.Font);

            this._contextMenuStrip.Font = this.Font;

            this._initialFontName = this.Font.Name;

            base.OnFontChanged(e);

            this.SizePages();

        }

        private void SetDefaultButtonTextAlign(ContentAlignment oldAlignment, ContentAlignment newAlignment)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].TextAlign == oldAlignment)
                {
                    this._navigationPageCollection[i].TextAlign = newAlignment;

                }

            }

        }

        private void SetDefaultButtonImageAlign(ContentAlignment oldAlignment, ContentAlignment newAlignment)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].ImageAlign == oldAlignment)
                {
                    this._navigationPageCollection[i].ImageAlign = newAlignment;

                }

            }

        }

        private void SetDefaultButtonForeColor(Color oldColor, Color newColor)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].ButtonForeColor == oldColor)
                {
                    this._navigationPageCollection[i].ButtonForeColor = newColor;

                }

            }

        }

        private void SetDefaultButtonGradientHighColor(Color oldColor, Color newColor)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].GradientHighColor == oldColor)
                {
                    this._navigationPageCollection[i].GradientHighColor = newColor;

                }

            }

        }

        private void SetDefaultButtonGradientLowColor(Color oldColor, Color newColor)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].GradientLowColor == oldColor)
                {
                    this._navigationPageCollection[i].GradientLowColor = newColor;

                }

            }

        }

        private void SetDefaultButtonActiveGradientHighColor(Color oldColor, Color newColor)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].ActiveGradientHighColor == oldColor)
                {
                    this._navigationPageCollection[i].ActiveGradientHighColor = newColor;

                }

            }

        }

        private void SetDefaultButtonActiveGradientLowColor(Color oldColor, Color newColor)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].ActiveGradientLowColor == oldColor)
                {
                    this._navigationPageCollection[i].ActiveGradientLowColor = newColor;

                }

            }

        }

        private void SetDefaultButtonHighlightGradientHighColor(Color oldColor, Color newColor)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].HighlightGradientHighColor == oldColor)
                {
                    this._navigationPageCollection[i].HighlightGradientHighColor = newColor;

                }

            }

        }

        private void SetDefaultButtonHighlightGradientLowColor(Color oldColor, Color newColor)
        {
            for (int i = 0; i < this._navigationPageCollection.Count; i++)
            {
                if (this._navigationPageCollection[i].HighlightGradientLowColor == oldColor)
                {
                    this._navigationPageCollection[i].HighlightGradientLowColor = newColor;

                }

            }

        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="factor"></param>
        /// <param name="specified"></param>
        protected override void ScaleControl(System.Drawing.SizeF factor, System.Windows.Forms.BoundsSpecified specified)
        {
            base.ScaleControl(factor, specified);

            this.SizePages();

        }

        /// <summary>
        /// 
        /// </summary>
        protected override void InitLayout()
        {
            base.InitLayout();

            this._initialFontName = this.Font.Name;

        }

    }

}
